package vip.rssc.configs;

import com.google.common.base.Function;
import com.google.common.base.Optional;
import com.google.common.base.Predicate;
import io.swagger.annotations.ApiOperation;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.lang.Nullable;
import springfox.documentation.RequestHandler;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.service.ApiKey;
import springfox.documentation.service.Contact;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;

import java.util.ArrayList;
import java.util.List;

/**
 * <p>Description: [SwaggerConfig]</p >
 * Created on 2022年05月15日
 *
 * @author <a href="chenjia@fehorizon.com">CJ</a>
 * @version 1.0
 * Copyright (c) 2022 上海宏信建设发展有限公司
 */
@Configuration
@EnableSwagger2
public class SwaggerConfig {

    // 定义分隔符,配置Swagger多包
    private static final String seperator = ";";

    @Bean
    public Docket docket() {
        String basePackages = "vip.rssc;";
        return new Docket(DocumentationType.SWAGGER_2)
            .apiInfo(apiInfo())
            .select()
            //加了ApiOperation注解的类，才生成接口文档
            .apis(RequestHandlerSelectors.withMethodAnnotation(ApiOperation.class))
            //包下的类，才生成接口文档
            .apis(basePackages(basePackages))
            .paths(PathSelectors.any())
            .build()
            .securitySchemes(security());
    }

    public static Predicate<RequestHandler> basePackages(final String packages){

        Predicate<RequestHandler> handler = new Predicate<RequestHandler>() {
            @Override
            public boolean apply(@Nullable RequestHandler input) {
                Optional<? extends Class<?>> ops = Optional.fromNullable(input.declaringClass());
                boolean result = ops.transform(handlerPackage(packages)).or(true);
                return result;
            }
        };
        return handler;
    }

    private static Function<Class<?>, Boolean> handlerPackage(final String basePackage)     {
        return input -> {
            // 循环判断匹配
            for (String strPackage : basePackage.split(seperator)) {
                boolean isMatch = input.getPackage().getName().startsWith(strPackage);
                if (isMatch) {
                    return true;
                }
            }
            return false;
        };
    }

    private ApiInfo apiInfo() {
        return new ApiInfoBuilder().
            title("swagger接口文档").
            contact(new Contact("rssc", "", "")).
            version("1.0").
            build();
    }

    private List<ApiKey> security() {
        List<ApiKey>  keyList = new ArrayList<>();
        ApiKey apikey = new ApiKey("token", "token", "header");
        keyList.add(apikey);
        apikey = new ApiKey("Authorization", "Authorization", "header");
        keyList.add(apikey);
        return keyList;
    }

}
